﻿using App.Common;
using QxFramework.Core;
using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using static App.Common.Data;
public class LightCheck : MonoBehaviour
{
    public EndAnim _endAnim;

    public Sprite _SuccessImage;

    public Sprite _FailImage;

    // Start is called before the first frame update
    public List<hexagon> cells;
    hexagon start;
    hexagon end;
    List<hexagon> Disposes;
    public GameObject LightOn;
    private List<GameObject> LightPool;
    List<hexagon> Paths;
    void Start()
    {
    }

    public void Init()
    {
        Transform levelTr = Data.Instance.levelMap.transform;

        for (int i = 0; i < levelTr.childCount; i++)
        {
            cells.Add(levelTr.GetChild(i).GetComponent<hexagon>());
        }
        LightPool = new List<GameObject>();
        Paths = new List<hexagon>();
        FindEnd();
        FindStart();
        StartCheck(false);
    }

    private void Update()
    {
        FindWays();
    }

    private void FindEnd()
    {
        foreach (var i in Maps.Instance.cells)
        {
            bool fake = false;
            foreach (var j in i.edges)
            {
                if (j != Edge.In)
                {
                    fake = true;
                    break;
                }
            }
            if (!fake)
            {
                end = i;
                return;
            }
                
            
            
        }
        Debug.Log("没有找到起点");
    }

    private void FindStart()
    {
        foreach (var i in Maps.Instance.cells)
        {
            bool fake = false;
            foreach (var j in i.edges)
            {
                if (j != Edge.Out)
                {
                    fake = true;
                    break;
                }
            }
            if (!fake)
            {
                start = i;
                start.IsConnected = true;
                return;
            }

        }
        Debug.Log("没有找到终点");
    }


    public bool StartCheck(bool TrulyPut)
    {
        
        Disposes = new List<hexagon>();
        foreach (var i in Maps.Instance.cells)
        {
           
            i.IsConnected = false;
            start.IsConnected = true;
            
        }
        Disposes.Add(start);
        DFSCheck(start);
        //Debug.Log(Disposes.Count + gameObject.name + LightPool.Count);
        foreach (var i in LightPool)
        {
            Destroy(i.gameObject);
        }

        LightPool = new List<GameObject>();
        
        foreach (var i in Disposes)
        {
            Light(i);
        }
        foreach (var i in Disposes)
        {
            if (i == end)
            {
                if (TrulyPut)
                {
                    Victory();
                 }
                 return  true;
            }
        }
        return false;
        
    }
    private void Light(hexagon now)
    {
        GameObject L = Instantiate(LightOn);
        L.transform.position = now.transform.position + new Vector3(0, 0, 2);
        LightPool.Add(L);
    }
    

    private void DFSCheck(hexagon start)
    {
        foreach (HexaDirect step in Enum.GetValues(typeof(HexaDirect)))
        {
            Vector3 direction = Data.Instance.dir2Vector[step];
            if (start.edges[(int)step] == Edge.Out){//如果这个方向上有出口
                //先检测这方向有没有地块
                Vector3 TargetPos = start.Pos + direction;
                if (!IsOverWall(TargetPos))//有地块
                {
                    hexagon next = FindHex(TargetPos);
                    if (!IsRepeated(Disposes, next))
                    {
                        Edge InputSide = next.edges[((int)step + 3) % 6];//6666666
                        if (InputSide == Edge.In)//联通成功
                        {
                            next.IsConnected = true;
                            Disposes.Add(next);
                            DFSCheck(next);
                        }
                    }
                    
                }
                
            }
        }
    }

    private bool IsRepeated(List<hexagon> L,hexagon now)
    {
        
        foreach(var i in L)
        {
            if (i == now)
            {
                return true;
            }
        }
        return false;
    }




    private bool IsOverWall(Vector3 vector)
    {
        if (Mathf.Abs(vector.x) == 3 || Mathf.Abs(vector.y) == 3 || Mathf.Abs(vector.z) == 3)
        {
            return true;
        }
        else
        {
            return false;
        }
    }
    private hexagon FindHex(Vector3 pos)
    {
        hexagon hexagon = null;
        foreach (var i in Maps.Instance.cells)
        {
            if (i.Pos == pos)
            {

                return i;
            }
        }
        Debug.Log("没有找到对应坐标");
        return hexagon;

    }

    private void Victory()
    {
        foreach(var i in LightPool)
        {
            Destroy(i);
        }
        LightPool = new List<GameObject>();
        FindWays();
        _endAnim = GameObject.Find("EndAnim").GetComponent<EndAnim>();

        StartCoroutine(EndCorotine());
    }

    private void FindWays()
    {
        Paths = new List<hexagon>();
        
        if (FindNext(start))
        {
            Paths.Add(start);
        }
    }

    private bool FindNext(hexagon now)
    {
        if (now == end)
        {
            return true;
        }
        else
        {
            foreach (HexaDirect step in Enum.GetValues(typeof(HexaDirect)))
            {
                Vector3 direction = Data.Instance.dir2Vector[step];
                if (now.edges[(int)step] == Edge.Out)
                {//如果这个方向上有出口
                 //先检测这方向有没有地块
                    Vector3 TargetPos = now.Pos + direction;
                    if (!IsOverWall(TargetPos))//有地块
                    {
                        hexagon next = FindHex(TargetPos);
                        if (!IsRepeated(Paths, next))
                        {
                            Edge InputSide = next.edges[((int)step + 3) % 6];//6666666
                            if (InputSide == Edge.In)//联通成功
                            {
                                bool  IsFind=   FindNext(next);
                                if (IsFind)
                                {
                                    Paths.Add(next);
                                }
                                return IsFind;
                            }
                        }

                    }

                }
                
            }

            return false;
        }
    }


    public void deleteAll()
    {
        foreach(GameObject gb in LightPool)
        {
            Destroy(gb.gameObject);
        }
        LightPool = new List<GameObject>();
    }

    IEnumerator EndCorotine()
    {
        yield return StartCoroutine(_endAnim.End(Paths));
        //Path
        Debug.Log("胜利");
        if (Data.Instance.nowLevel + 1 <= Data.Instance.levelNum)
        {
            UIBase ui=UIManager.Instance.Open("DialogWindowUI", "DialogWindowUI", new DialogWindowUI.DialogWindowUIArg("成功", "你通关了", _SuccessImage, "下一关", "结束游戏", () => {
                Data.Instance.LoadLevel(Data.Instance.nowLevel + 1);
                deleteAll();
                CardManager.Instance.InitCards();
            }));
            ui.Get<Image>("MaskPanel").sprite = _SuccessImage;
        }
        else
        {
            UIBase ui = UIManager.Instance.Open("DialogWindowUI", "DialogWindowUI", new DialogWindowUI.DialogWindowUIArg("成功", "你通关了", _FailImage, "结束游戏", () => {
                Application.Quit();
            }));
            ui.Get<Image>("MaskPanel").sprite = _SuccessImage;
        }
    }
}
